home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Magnum One
/
Magnum One (Mid-American Digital) (Disc Manufacturing).iso
/
d18
/
filemod2.arc
/
FILEMOD2.ASM
next >
Wrap
Assembly Source File
|
1991-04-28
|
36KB
|
1,797 lines
;FILEMOD2 latest bug fix 15 May 89 = FILEMOD2.ZIP
cr EQU 0Dh
lf EQU 0Ah
tab EQU 9
CSEG segment byte public
assume CS:CSEG, DS:CSEG, ES:CSEG, SS:CSEG
ORG 0100h
Start: JMP Begin
NoNameMsg DB 'FileMod2 Byte Editor 5/89 by J. E. Arkay',cr,lf,cr,lf
DB 'Syntax: FILEMOD2 [d:][\path\]filename.ext',cr,lf
DB 'Hit F1 for help.',cr,lf,'$',1Ah
VideoSeg DW 0
Ten DW 10
ParamCount DB 0,0
CmdLineBuf DB 7Eh DUP (0)
CmdLineByteCount DW 0
DB 'Video Attributes:'
LineNoAttr DB 0Ch,'=LINE NOS'
HexDisplAttr DB 6,'=HEX DISPLAY'
HexCrsrAttr DB 0F0h,'=HEX EDIT CRSR'
ASCIIdisplAttr DB 7,'=ASCII DISPLAY'
ActCrsrAttr DB 70h,'=ACTIVE CRSR'
PassCrsrAttr DB 1,'=SLAVE CRSR'
HelpAttr DB 74h,'=HELP SCREEN'
HelpBrdrAttr DB 1Ch,'=HELP BORDER'
ActiveScrn DB 0,'=BOOT ACTIVE' ;0 = ASCII, 1 = Hex field active
GraphChars DB 0,'=GRAPHIC CHARS'
HexPfx DB '_','=HEX PFX'
CrsrType DW 0
COMflag DB 0 ;set to 1 if .COM file loaded
FNameToShow DB 80h DUP (0)
ReadBuf DB 100h DUP (0)
Buf2 DB 100h DUP (0) ; MUST follow ReadBuf
Handle DW 0
LastRecLo DB 0
LastRecHi DB 0
BytesRead DW 0
CurrRecLo DB 1
CurrRecHi DB 0
UnsavedFlag DB 0
H003E6 DB 0
HexPointer DW 322 ;decimal, 161st char, 2nd on 3rd line
ASCIIpntr DW 444 ;222nd char
HexCrsrLocn DW 6
H0040C DW 0
KeystrokeAX DW 0
H00410 DB 0
SearchMode DB 0
SrchForStr DB 'Search for: '
InputString DB 41 DUP (0) ; MUST follow SrchForStr
HexString DB 41 DUP (0)
BytesToSearch DB 0,0 ;accessed as WORD in Search
BytesInput DB 0,0 ; ditto
ByteNo DB 0,0 ; ditto
LastByte DB 0,0 ; ditto
RecNumBuf DB 5,0
RecNumInput DB 0,0,0,0,0,0 ; MUST follow RecNumBuf
SModeStr DB 'Use ═ ═ keys: ' ;16 bytes
DB 'Case-Insens Exact Hex ' ;33 bytes
;these are in reverse order of VecTbl. Must change number at ChkOurKeys
; if you add a function !
DB 'SCAN CODE TABLE:'
ScanCodeTbl DB 42h,3Ch,44h,40h,47h,4Fh,0Fh,4Bh,0Eh
DB 4Dh,48h,50h,75h,77h,84h,76h,49h,51h,43h,3Bh,1
VecTbl DW offset ESCpgm ;exit pgm (not help)
DW offset F1 ;help
DW offset F9 ;save record
DW offset PgDn
DW offset PgUp
DW offset CtrlPgDn
DW offset CtrlPgUp
DW offset CtrlHome
DW offset CtrlEnd
DW offset UpDnArrow
DW offset UpDnArrow
DW offset RightLeftBksp
DW offset RightLeftBksp
DW offset RightLeftBksp
DW offset TabScreen ;switch active field
DW offset EndKey
DW offset HomeKey
DW offset F6 ;toggle non-ASCII characters
DW offset F10 ;new record
DW offset F2 ;search
DW offset DoSearch ;F8, repeat search
OpenErrMsg DB ' File Open error, code is '
ErrCode DB '00',cr,lf,'$'
;each of these is 16d bytes long:
Err2 DB 'File not found $'
Err3 DB 'Path not found $'
Err4 DB 'Too many files $'
Err5 DB 'Access denied $'
CrLf$ DB cr,lf,'$'
ASCII$ DB 'ASCII'
_HEX_$ DB ' HEX '
NoEnteredStr DB 'No String Entered',0
InvalidStr DB 'Invalid',0
UnsavedStr DB 'Unsaved changes - Hit F9 to save, any '
DB 'other key to continue',0
RecSavStr DB 'Record saved',0
RecNumStr DB 'Record number:',0
SrchFoundStr DB 'Search string found',0
SrchFailedStr DB 'Search failed',0
SrchAbortStr DB 'Search cancelled',0
DB 10 DUP ('Stack ')
ScreenStart DB 80 dup (' ',7) ;byte numbers go here
;2nd line:
DB 3 dup (' ',7)
DB '┌',7
DB 48 dup ('─',7)
DB 28 dup (' ',7)
FirstLineNo DB 7 dup (' ',7),' '
HexSpaces DB 7
DB 45 dup (' ',7)
DB 'R',4,'e',4,'c',4,'o',4,'r',4,'d',4,' ',4
DB '│',7,18 dup (' ',7),'│',7
;4th line:
DB 54 dup (' ',7)
CurRec DB 6 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;5th line:
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;6th line:
DB 54 dup (' ',7)
DB 'L',4,'a',4,'s',4,'t',4,' ',4,' ',4
DB '│',7,18 dup (' ',7),'│',7
;7th line:
DB 54 dup (' ',7)
LastRecLoc DB 6 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;8th line:
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;9th line:
DB 54 dup (' ',7)
DB 'B',4,'y',4,'t',4,'e',4,' ',7,' ',7
DB '│',7,18 dup (' ',7),'│',7
;10th line:
DB 55 dup (' ',7)
DB 2 dup (' ',0Ch) ;byte no. goes here
DB 3 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;11th line:
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;12th line:
DB 55 dup (' ',7)
DB '',4
DB 4 dup (' ',4)
DB '│',7,18 dup (' ',7),'│',7
;13th line:
DB 53 dup (' ',7)
DB ' ',4,'H',4,'e',4,'x',4,' ',4,' ',4,' ',4
DB '│',7,18 dup (' ',7),'│',7
;14th line:
DB 53 dup (' ',7)
DB 'V',4,'a',4,'l',4,'u',4,'e',4,'s',4,' ',4
DB '│',7,18 dup (' ',7),'│',7
;15th line:
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
DB 60 dup (' ',7)
DB '│',7,18 dup (' ',7),'│',7
;19th line:
DB 80 dup (' ',7)
FileNameLoc DB 62 dup (' ',7)
DB '┌',7,14 dup ('─',7),'┐',7,' ',7,' ',7
;21st line:
DB 62 dup (' ',7)
DB '│',7,' ',17h,'F',17h,'i',17h,'l',17h,'e',17h
DB 'M',17h,'o',17h,'d',17h,' ',17h
DB 'V',17h,'2',17h,'.',17h,'0',17h,' ',17h,'│',7,' ',7,' ',7
;22nd line:
DB 62 dup (' ',0Eh),'└',7,14 dup ('─',7),'┘',7,' ',7,' ',7
DB 80 dup (' ',7)
;24th line:
DB 'F',70h,'1',70h,'=',5,'H',5,'e',5,'l',5,'p',5
DB ' ',5
DB 'F',70h,'2',70h,'=',5,'S',5,'e',5,'a',5,'r',5,'c',5,'h',5
DB ',',5
DB 'F',70h,'8',70h,'=',5,'R',5,'e',5,'p',5,'e',5,'a',5,'t',5
DB ' ',5
DB 'F',70h,'6',70h,'=',5,'S',5,'e',5,'e',5,' ',5
DB 'C',5,'h',5,'r',5,'$',5
DB ' ',5
DB 'T',70h,'a',70h,'b',70h,'=',5,'C',5,'h',5,'g',5,' ',5
DB 'f',5,'i',5,'e',5,'l',5,'d',5,'s',5
DB ' ',5
DB 'F',70h,'1',70h,'0',70h,'=',5,'N',5,'e',5,'w',5,' ',5
DB 'R',5,'e',5,'c',5
DB 3 dup (' ',5)
DB 'F',70h,'9',70h,'=',5,'S',5,'a',5,'v',5,'e',5
DB ' ',5,'R',5,'e',5,'c',5
;25th line:
DB ' ',5,'E',70h,'s',70h,'c',70h,'=',5,'E',5,'x',5,'i',5,'t',5
DB 3 dup (' ',5)
DB '^',70h,'H',70h,'o',70h,'m',70h,'e',70h,'=',5
DB '1',5,'s',5,'t',5,' ',5,'B',5,'y',5,'t',5,'e',5
DB ' ',5
DB '^',70h,'E',70h,'n',70h,'d',70h,'=',5,'L',5,'a',5,'s',5,'t',5
DB ' ',5,'B',5,'y',5,'t',5,'e',5,' ',5
DB 'P',70h,'g',70h,'D',70h,'n',70h,'/',5,'U',70h,'p',70h,'=',5
DB 'N',5,'e',5,'x',5,'t',5,' ',5,'R',5,'e',5,'c',5
DB ' ',5
DB '^',70h,'P',70h,'g',70h,'D',70h,'n',70h,'/',5,'U',70h,'p',70h
DB '=',5,'L',5,'a',5,'s',5,'t',5,'/',5,'1',5,'s',5,'t',5
DB ' ',5,'R',5,'e',5,'c',5
HelpBottom DB '──── ESC=Exit ─────────────────' ;62 chars
DB '──────── use PgUp PgDn ────'
;each line is 62 chars, including at least 1 space at each end
HelpMsg DB ' FileMod runs in CGA or Mono mode.',0
DB ' Records are 256d bytes. TAB toggles the active field',0
DB ' between Hex and ASCII. The large cursor is active.',0
DB ' You must hit both characters of a Hex number.',0
DB ' If you load a .COM file, the first record is 1; otherwise,',0
DB ' the first record is 0.',0
DB 0
DB ' Home, End, and the cursor keys work normally.',0
DB 0
DB ' Searching (F2 or CTRL-S): Put no quotes around text.',0
DB ' Max length of search string is 40 characters. You can',0
DB ' put Hex numbers in ASCII searches by preceding with HEX PFX '
DB ' char (default is _). Example:',0
DB ' HELLO_0D_0a searches for HELLO,cr,lf',0
DB ' ESC or F2 cancels string entry.',0
DB ' In Hex mode, enter both characters and separate with space.',0
DB 0
;page 2:
DB ' CHANGING DEFAULTS',0
DB ' Many default settings can be changed by using FileMod on '
DB ' itself. Starting in Record 0002 (following the string Video '
DB ' Attributes) you''ll find 11 items shown as byte=NAME.',0
DB ' Make sure you have a backup copy of FileMod.',0
DB ' TAB over to the Hex field and put the cursor on the byte',0
DB ' before =ASCII DISPLAY. It is 07, for white on black. '
DB ' If, for example, you change it to 1E the ASCII part of the '
DB ' screen will be yellow on blue.',0
DB 0
DB ' You can also change the 21 action keys. Their scan codes '
DB ' follow the string SCAN CODE TABLE:.',0
DB 0
DB ' Send complaints or money to:',0
DB ' J. E. Arkay PO Box 9747 Baltimore, MD 21204',0
DB 0
DB 0
MaxMove DB 17 ;max no of lines moved = 1 page
HelpLineCount DB 0
Begin: MOV AX,OFFSET ScreenStart
MOV SP,AX
MOV SI,80h
MOV DI,OFFSET ParamCount
MOV CX,80h
CLD
REP MOVSB
XOR CX,CX
MOV CL,ParamCount
MOV CmdLineByteCount,CX
CALL SetVideoSeg
CALL GetTargetName
JC Abort
CALL OpenFile
JC Abort
CALL GetFileStats ;does Last record no.
JC Abort
CALL TabScreen
CALL CopyHexDisplAttr
CALL ShowFNameAndDate
CALL ShowLineNos
CALL ShowCurrRec
CALL MoveAndRead
CALL SetCrsrType
KeyLoop:
CALL GetKey
JNC KeyLoop
;Carry signals ESC is hit, exit the pgm
CALL RestoreCrsr
Abort: MOV BX,Handle
MOV AH,3Eh ;Close File
INT 21h
MOV AX,4C00h ;exit with Errorlevel 0
INT 21h
; - - - - - - - - - - - - - - - - - -
GetKey: MOV AH,1 ;Report kbd char
INT 16h
JZ KBufClear
XOR AH,AH ;clears the kbd buffer
INT 16h
JMP SHORT GetKey
KBufClear:
XOR AH,AH ;Wait for kbd character
INT 16h
ChkOurKeys:
PUSH AX ;save scan codes
MOV AH,2 ;get shift key status
INT 16h
MOV BL,AL ;save shift status
POP AX
TEST BL,00000100b ;CTRL key depressed ?
CMP AL,13h
JNZ NoShifts
JMP F2 ;CTRL-s does search, too
NoShifts:
XCHG AL,AH
MOV CX,21 ;21d entries
MOV DI,OFFSET ScanCodeTbl
REPNZ SCASB
JZ Vector
CMP ActiveScrn,0
JNZ HexActive
CALL ASCIIactive
CMP H003E6,0
JZ GetKey
MOV H003E6,0
JMP SHORT NoShifts
HexActive:
CALL H01CF8
JMP SHORT GetKey
Vector: SHL CX,1
MOV DI,CX
JMP WORD PTR [DI+offset VecTbl]
ASCIIactive:
CALL ChkHexKey
JNC NotHex
JMP RetWithNC
NotHex: MOV CL,4
SHL AL,CL
XOR BH,BH
MOV BL,ByteNo
MOV SI,BX
MOV CL,BYTE PTR [SI+offset ReadBuf]
MOV H00410,CL
AND BYTE PTR [SI+offset ReadBuf],00001111b
OR BYTE PTR [SI+offset ReadBuf],AL
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
PUSH ES
MOV ES,WORD PTR DS:VideoSeg
MOV CX,HexCrsrLocn
MOV SI,CX
MOV CL,HexCrsrAttr
MOV BYTE PTR ES:1[SI],CL
POP ES
XOR AH,AH
INT 16h ;wait for Kbd char
MOV KeystrokeAX,AX
MOV AH,AL ;ASCII code
CALL ChkHexKey
JC NotaHexHit
XOR BH,BH
MOV BL,ByteNo
MOV SI,BX
AND AL,00001111b
AND BYTE PTR [SI+offset ReadBuf],11110000b
OR BYTE PTR [SI+offset ReadBuf],AL
MOV UnsavedFlag,1
INC ByteNo
JNZ NotAtFF
DEC ByteNo ;limit INC to FF max
NotAtFF:
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
JMP SHORT RetWithNC
NotaHexHit:
MOV AL,H00410
XOR BH,BH
MOV BL,ByteNo
MOV SI,BX
MOV BYTE PTR [SI+offset ReadBuf],AL
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
MOV AX,KeystrokeAX
MOV H003E6,1
RetWithNC:
CLC
RET
ChkHexKey:
MOV AL,AH
CALL UpCaseAndCifNotASCII
MOV AH,AL
JC SetCarry
CMP AH,'9' ;39h
JNA Numbr
CMP AH,'A' ;41h
JB SetCarry ;above 9 and below A is not a Hex char
MOV AL,AH
SUB AL,7 ;for letters only
Numbr: SUB AL,30h
JC SetCarry
CMP AL,0Fh
JA SetCarry
CLC
RET
SetCarry:
STC
RET
H01CF8: CMP AH,' ' ;20h
JC RET1
CMP AH,7Eh ;highest printable code, '~'
JA RET1
XOR BH,BH
MOV BL,ByteNo
MOV SI,BX
MOV BYTE PTR [SI+offset ReadBuf],AH
INC ByteNo
JNZ NoDEC
DEC ByteNo
NoDEC:
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
MOV UnsavedFlag,1
RET1: RET
; - - - - - - - - - - - - - - - - - -
F10: CALL PaintScreen
CALL ShoCursors
CMP UnsavedFlag,0
JZ H01D37
CALL AskSave
H01D37:
MOV SI,OFFSET RecNumStr
CALL ShoOnMsgLine
MOV AH,2 ;set crsr position
MOV DH,15h ;row
MOV DL,0Fh ;column
MOV BH,0 ;display page
INT 10h
MOV AH,0Ah ;buffered kbd input
MOV DX,OFFSET RecNumBuf ;points to input buffer (max length 1st)
INT 21h
MOV SI,offset RecNumInput
XOR BX,BX
MOV CL,4
RecKeyLoop:
LODSB
CMP AL,cr
JZ RecNoEntered
MOV AH,AL
CALL ChkHexKey
JC InvalidRec
SHL BX,CL
OR BL,AL
JMP SHORT RecKeyLoop
RecNoEntered:
CMP COMflag,0
JNZ OldWay
INC BX
OldWay: CMP BX,WORD PTR DS:LastRecLo
JA UseLast
OR BX,BX
JNZ RecNoOK
MOV BX,1 ;if 0 was entered
JMP RecNoOK
UseLast:
MOV BX,WORD PTR DS:LastRecLo
RecNoOK:
MOV WORD PTR DS:CurrRecLo,BX
CALL MoveAndRead
RET
InvalidRec:
CALL PaintScreen
CALL ShoCursors
MOV SI,OFFSET InvalidStr
CALL ShoOnMsgLine
RET
; - - - - - - - - - - - - - - - - - -
;exit pgm here
ESCpgm:
CMP UnsavedFlag,0
JZ H01DCE
CALL AskSave
H01DCE:
STC
RET
; - - - - - - - - - - - - - - - - - -
MoveAndRead:
;move pointer necessary because Search may have moved the file pointer
MOV AH,42h ;Move file pointer
MOV BX,Handle
MOV DX,WORD PTR DS:CurrRecLo
DEC DX
XOR AL,AL ;move to CX:DX
XOR CX,CX
MOV CL,DH
MOV DH,DL
XOR DL,DL ;now CX:DX = DX * 256
INT 21h
;read a record
MOV AH,3Fh ;Read From File
MOV CX,100h
MOV DX,OFFSET ReadBuf
MOV BX,Handle
INT 21h
OR AX,AX ;Attempt to read at EOF ?
JNZ NotEOF
DEC WORD PTR DS:CurrRecLo
JMP SHORT MoveAndRead
NotEOF: MOV BytesRead,AX
OR AL,AL ;even record read ?
JZ RecFilled
MOV DI,AX
ADD DI,offset ReadBuf
NEG AX
ADD AX,100h
MOV CX,AX
MOV AL,' ' ;spaces for ASCII field, PaintHexAndASCII
REP STOSB ; puts blanks in Hex field
RecFilled:
CALL ShowCurrRec
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
MOV AX,WORD PTR DS:CurrRecLo
CLC
RET
; - - - - - - - - - - - - - - - - - -
;toggle displaying of graphic characters
F6: DEC GraphChars
NEG GraphChars
CALL PaintHexAndASCII
CALL PaintScreen
CALL ShoCursors
RET
; - - - - - - - - - - - - - - - - - -
ChkSearchStr:
;copy the string to HexString
MOV CX,WORD PTR BytesInput
MOV DI,offset HexString
CMP SearchMode,2 ;Hex mode ?
JNZ NoShove
MOV BYTE PTR [DI],' ' ;initial space so can use same routine
INC DI
NoShove:
MOV SI,offset InputString
REP MOVSB
;set up for checking
MOV DI,offset HexString
MOV CX,WORD PTR BytesInput
CMP SearchMode,2 ;Hex mode ?
JNZ Abcd
INC CX
Abcd: MOV BytesToSearch,CL
ChkSrchLoop:
MOV AL,HexPfx ;do nothing unless hex pfx found
CMP SearchMode,2 ;Hex mode ?
JNZ HexStart
;in Hex mode, char before a hex pair must be space
MOV AL,' '
HexStart:
REPNZ SCASB
JNZ RETwithNoC
;a Hex Prefix character or space has been found
HereIsHex:
MOV AH,BYTE PTR [DI]
CALL ChkHexKey
JC RETwithC ;if invalid entry
MOV BH,CL ;save HexString count
MOV CL,4
SHL AL,CL
MOV CL,BH ;restore HexString count
MOV BL,AL
MOV AH,BYTE PTR 1[DI] ;2nd byte of hex no.
CALL ChkHexKey
JC RETwithC ;if invalid entry
OR AL,BL
MOV BYTE PTR -1[DI],AL ;store binary byte where pfx/space was
SUB BytesToSearch,2
JS RETwithC ;if at end of string
MOV SI,DI
ADD SI,2
PUSH DI
REP MOVSB ;squeeze the string
POP DI
MOV CL,BH
SUB CL,2
JZ RETwithNoC
JS RETwithC
JMP SHORT ChkSrchLoop
RETwithC:
STC
RET
RETwithNoC:
CLC
RET
; - - - - - - - - - - - - - - - - - -
;inverse the search mode, show search string. Returns DI > next char on msg line
ShowMode:
PUSH SI
PUSH CX
PUSH ES
MOV AX,DS
MOV ES,AX
CALL ClearFNameAtt
MOV DI,offset FileNameLoc
ADD DI,33 ;point 1st attrib byte
MOV AX,22
MUL SearchMode
ADD DI,AX
MOV AL,78h
MOV CX,11
SMInvLoop:
STOSB
INC DI
LOOP SMInvLoop
CALL PaintScreen
CALL ShoCursors
MOV SI,OFFSET SrchForStr
CALL ShoOnMsgLine
POP ES
POP CX
POP SI
RET
ClearFNameAtt:
MOV DI,offset FileNameLoc
INC DI
MOV AL,7
JMP Paint62
; - - - - - - - - - - - - - - - - - -
F2: CALL PaintScreen
CALL ShoCursors
CMP UnsavedFlag,0
JZ EnterSearchStr
CALL AskSave
EnterSearchStr:
;show "Case-Insens Exact Hex " at 20th line
MOV DI,offset FileNameLoc
MOV SI,offset SModeStr
MOV CX,49
SModeLoop:
MOVSB
INC DI
LOOP SModeLoop
MOV AL,' '
MOV AH,7
MOV CX,13
REP STOSW
CALL ShowMode ;puts DI just past the 'Search String: xxxxx'
PUSH ES
MOV ES,VideoSeg
SrchKeyLoop:
XOR AH,AH ;wait for a keystroke
INT 16h
OR AL,AL ;function or control key ?
JNZ NoSpecial
CMP AH,3Ch ;F2 hit ?
JZ SchEsc
CMP AH,4Dh ;right arrow ?
JNZ NotR
CMP SearchMode,2
JZ SrchKeyLoop
INC SearchMode
CALL ShowMode
JMP SrchKeyLoop
NotR: CMP AH,4Bh ;left arrow ?
JNZ SrchKeyLoop
CMP SearchMode,0
JZ SrchKeyLoop
DEC SearchMode
CALL ShowMode
JMP SrchKeyLoop
NoSpecial:
CMP AL,1Bh ;ESC hit ?
JNZ NoEsc
SchEsc: POP ES
JMP Scape
NoEsc: CMP AL,cr
JZ EndStr
CMP AL,8 ;backspace ?
JNZ NoBS
CMP BytesInput,0
JZ SrchKeyLoop
DEC BytesInput
DEC DI
DEC DI
MOV BYTE PTR ES:[DI],' '
MOV SI,offset InputString
ADD SI,WORD PTR DS:BytesInput
MOV BYTE PTR [SI],0
JMP SrchKeyLoop
NoBS: CMP BytesInput,39
JBE StoIt
MOV DL,7 ;beep
MOV AH,2 ;display character
INT 21h
JMP SrchKeyLoop
StoIt: STOSB
INC DI
MOV SI,offset InputString
ADD SI,WORD PTR DS:BytesInput
MOV BYTE PTR [SI],AL
INC BytesInput
JMP SrchKeyLoop
;ENTER has been hit
EndStr: INC SI
MOV BYTE PTR [SI],0
POP ES
CALL ChkSearchStr
JNC DoSearch
MOV SI,OFFSET InvalidStr
JMP PaintNend
DoSearch: ; ~20FC in code
CMP BytesInput,0
JNZ StrOK
MOV SI,offset NoEnteredStr
JMP PaintNend
StrOK: MOV SI,OFFSET SrchForStr
CALL ShoOnMsgLine
CALL MoveAndRead ;******
CALL ReadRec2
CMP WORD PTR DS:ByteNo,0FFh
JAE NotThisRec ;search starts 1st of next record
ADD DI,WORD PTR DS:ByteNo
INC DI ;start 1 past cursor
SUB CX,WORD PTR DS:ByteNo
DEC CX ;bytes left past cursor
ScanNewRec:
MOV BX,WORD PTR DS:LastRecLo
CMP BX,WORD PTR DS:CurrRecLo
JNZ KeepScanning
;This is the last record. Set CX = remaining bytes & stop if at EOF
ADD CX,WORD PTR DS:LastByte
SUB CX,0FFh ;if Last=0, still must check 1 byte.
JBE NotThisRec
KeepScanning:
MOV AL,HexString ;get 1st byte
CMP SearchMode,0 ;Case-Insensitive ?
JNZ Quick
;look for a match on the 1st byte of the search string
;.....for Case-Insens only .........
CALL UpCaseLetter
MOV AH,AL
SlowLoop:
MOV AL,[DI]
INC DI
CALL UpCaseLetter
CMP AL,AH
JZ Found1st
LOOP SlowLoop
JMP NotThisRec
;....................................
Quick: REPNZ SCASB ;cmp AL - ES:[DI] and inc DI
;will inc DI again after 1st non-match, ends w/DI->1 past match
JZ Found1st ;w/CX=bytes left past find
NotThisRec:
INC WORD PTR DS:CurrRecLo
MOV BX,WORD PTR DS:LastRecLo
CMP BX,WORD PTR DS:CurrRecLo
JC SearchFailed
MOV AH,1 ;report kbd char if available
INT 16h
JNZ Cancel ;if char, stop search
;move Buf2 up into ReadBuf
MOV SI,offset Buf2
MOV DI,offset ReadBuf
MOV CX,100h
REP MOVSB
CALL ReadRec2 ;next 256 bytes -> Buf2, CX=100h, DI>ReadBuf
JMP ScanNewRec
;a match has been found on the 1st byte of the search string.
Found1st: ;scan whole string, may run into Buf2
;first, see if file ends before string length
MOV AX,CX ;remaining bytes past find in ReadBuf
INC AX ;we'll check the found byte, too
MOV BX,WORD PTR DS:LastRecLo
SUB BX,WORD PTR DS:CurrRecLo
CMP BX,1
JB InLast
JNZ EnuffLeft
;we're in next-to-last record
ADD AX,WORD PTR DS:LastByte
INC AX ;'cause if LastByte is 0, still adds 1
InLast: CMP AX, WORD PTR DS:BytesToSearch
JB SearchFailed
EnuffLeft:
PUSH DI ;points 1 past find
PUSH CX ;remaining bytes past find in ReadBuf
DEC DI ;to found byte
MOV CX,WORD PTR DS:BytesToSearch
MOV SI,OFFSET HexString
CMP SearchMode,0 ;Case-Insensitive ?
JNZ QuickWhole
;.....for Case-Insens only .........
SlowWholeLoop:
LODSB ;get byte [SI] & INC SI
CALL UpCaseLetter
MOV AH,AL
MOV AL,[DI]
INC DI
CALL UpCaseLetter
CMP AL,AH
JNZ ScanDone
LOOP SlowWholeLoop
JMP SHORT ScanDone
;....................................
QuickWhole:
REPZ CMPSB ;cmp DS:SI - ES:DI and inc SI & DI
ScanDone:
POP CX ;remaining bytes past 1st find in Buf
POP DI ;points 1 past 1st find
JZ ShowTheFind ;every byte matched
JMP KeepScanning
SearchFailed:
MOV AL,LastByte
MOV ByteNo,AL
MOV SI,OFFSET SrchFailedStr
JMP PaintNend
;search cancelled by a keystroke
Cancel: MOV AH,0 ;Wait for char, removes from kbd buf
INT 16h ; (does not wait)
Scape: MOV SI,OFFSET SrchAbortStr
JMP PaintNend
ShowTheFind:
CMP DI,offset Buf2 ;have we scanned past end of ReadBuf ?
JB NoRollOver
INC WORD PTR DS:CurrRecLo ;if so, we're in the next record
NoRollOver:
SUB DI,offset ReadBuf
DEC DI
MOV WORD PTR DS:ByteNo,DI
MOV SI,OFFSET SrchFoundStr
PaintNend:
PUSH SI
CALL MoveAndRead
CALL ClearFNameAtt
CALL ShowFNameAndDate
CALL PaintScreen
CALL ShoCursors
POP SI
CALL ShoOnMsgLine
CLC
RET
ReadRec2:
MOV AH,3Fh ;Read From File
MOV CX,100h ;bytes to read
MOV DX,OFFSET Buf2
MOV BX,Handle
INT 21h
MOV CX,100h
MOV DI,offset ReadBuf
RET
; - - - - - - - - - - - - - - - - - -
AskSave:
MOV SI,OFFSET UnsavedStr
CALL ShoOnMsgLine
MOV AH,0 ;Wait for Kbd char
INT 16h
CMP AH,43h ;scan code = F9 ?
JNZ NoSave
CALL F9
NoSave:
MOV UnsavedFlag,0
CALL PaintScreen
CALL ShoCursors
RET
; - - - - - - - - - - - - - - - - - -
PgDn: CMP UnsavedFlag,0
JZ H02022
CALL AskSave
H02022: ADD WORD PTR DS:CurrRecLo,1 ;INC doesn't affect Carry !
JNC H0202D
DEC WORD PTR DS:CurrRecLo
H0202D: CALL MoveAndRead
CLC
RET
PgUp: CMP UnsavedFlag,0
JZ H0203C
CALL AskSave
H0203C: DEC WORD PTR DS:CurrRecLo
JNZ H02046
INC WORD PTR DS:CurrRecLo
H02046: CALL MoveAndRead
CLC
RET
CtrlPgDn:
CMP UnsavedFlag,0
JZ H02055
CALL AskSave
H02055: MOV AX,WORD PTR DS:LastRecLo
MOV WORD PTR DS:CurrRecLo,AX
CALL MoveAndRead
CLC
RET
CtrlPgUp:
CMP UnsavedFlag,0
JZ H02069
CALL AskSave
H02069: MOV WORD PTR DS:CurrRecLo,1
MOV ByteNo,0 ;cursor to upper left
CALL MoveAndRead
CLC
RET
RightLeftBksp:
MOV CL,ByteNo
CMP AL,4Dh ;right arrow ?
JNZ LeftArrow ;backspace treated like left arrow
;right arrow:
INC CL
JNZ GoRtLeft
;trap prevents annoying wraparound if file ends on last byte of last line
MOV AX,WORD PTR LastRecLo
CMP AX,WORD PTR CurrRecLo
JNZ GoNxPg
;we're in the last record and ByteNo would wrap around to 0
CLC
RET
GoNxPg: MOV ByteNo,0
JMP PgDn ;calls ShoCursors, traps past EOF
LeftArrow:
SUB CL,1
JNC GoRtLeft ;DEC does NOT AFFECT the C flag !
CMP WORD PTR DS:CurrRecLo,1
JNZ PrevRec
CLC
RET
PrevRec:
MOV ByteNo,0FFh
JMP PgUp
GoRtLeft:
MOV ByteNo,CL
CALL ShoCursors
CLC
RET
UpDnArrow:
CMP AL,48h ;up arrow ?
JNZ DownArrow
SUB ByteNo,10h
JNC H02121
;we have moved up into the previous record
CMP WORD PTR DS:CurrRecLo,1
JNZ UpRec
ADD ByteNo,10h
CLC
RET
UpRec: OR ByteNo,11110000b
JMP PgUp
DownArrow:
;trap prevents annoying jump to last byte from line above byte past end
; and wraparound if file ends on last line
MOV AX,WORD PTR LastRecLo
CMP AX,WORD PTR CurrRecLo
JNZ GoDown
;we're in the last record
MOV CL,ByteNo
CMP CL,0F0h ;in the last line ?
JAE Nope
ADD CL,10h
CMP CL,LastByte
JBE GoDown
Nope: CLC
RET
GoDown: ADD ByteNo,10h
JNC H02121
;we have moved down into the next record
AND ByteNo,00001111b
JMP PgDn
H02121: CALL ShoCursors
CLC
RET
EndKey: OR ByteNo,00001111b
JMP SHORT H02121
HomeKey:
AND ByteNo,11110000b
JMP SHORT H02121
CtrlHome:
MOV ByteNo,0
JMP SHORT H02121
CtrlEnd:
MOV ByteNo,0FFh
JMP SHORT H02121
; - - - - - - - - - - - - - - - - - -
F9: MOV SI,OFFSET RecSavStr
CALL ShoOnMsgLine
MOV AH,42h ;Move File Pointer
MOV DX,WORD PTR DS:CurrRecLo
DEC DX
MOV AL,0 ;move to CX:DX
XOR CX,CX
MOV CL,DH
MOV DH,DL
XOR DL,DL
MOV BX,Handle
INT 21h
MOV AH,40h ;Write to file
MOV CX,BytesRead ;Bytes to write
MOV DX,OFFSET ReadBuf
MOV BX,Handle
INT 21h
MOV UnsavedFlag,0
CLC
RET
PaintHexAndASCII:
XOR DH,DH ;byte counter
MOV DL,LastByte ;for faster compare
MOV SI,OFFSET ReadBuf
MOV HexPointer,014Ah ;165th char, 6th on 3rd line
MOV ASCIIpntr,01BCh
EachLine:
MOV CX,16 ;do 16d times
EachByte:
LODSB
MOV AH,HexDisplAttr
PUSH SI
MOV BX,WORD PTR DS:LastRecLo
CMP BX,WORD PTR DS:CurrRecLo
JNZ NotPast
;if past LastByte, print blanks in Hex field
CMP DH,DL
JBE NotPast
PUSH AX
MOV AL,0
CALL PrintHex
CALL PrintHex
ADD HexPointer,2
POP AX
JMP DoASC
NotPast:
CALL Print2atHexP
DoASC: MOV AH,ASCIIdisplAttr
CALL Print1atAsciiP ;already spaces if past end
POP SI
INC DH ;bump byte counter
LOOP EachByte
ADD HexPointer,40h
ADD ASCIIpntr,80h
OR DH,DH ;rolls over after last byte
JNZ EachLine
RET
; - - - - - - - - - - - - - - - - - -
TabScreen:
DEC ActiveScrn ;0->FF 1->0
NEG ActiveScrn ;FF=-1,->1 -0=0
MOV BH,'│'
MOV BL,'█'
MOV DH,'─'
MOV DL,'▀'
CMP ActiveScrn,0
JNZ HexLines
XCHG BH,BL
XCHG DH,DL
HexLines:
MOV DI,326+offset ScreenStart ;decimal
MOV CX,16
VertLoop:
MOV AL,BH
STOSB
ADD DI,113
MOV AL,BL
STOSB
ADD DI,37
STOSB
ADD DI,7
LOOP VertLoop
MOV DI,166+offset ScreenStart
MOV AL,'█'
CMP ActiveScrn,0
JZ HexCorner
MOV AL,'┌'
HexCorner:
STOSB
MOV AL,DH
MOV CX,48
HorLoop:
INC DI
STOSB
LOOP HorLoop
CALL PaintScreen
CALL ShoCursors
CLC
RET
; - - - - - - - - - - - - - - - - - -
Print2atHexP:
PUSH CX
PUSH AX
MOV CL,4
MOV CH,AL
ROR AL,CL
AND AL,00001111b
ADD AL,30h
CMP AL,'9' ;39h
JNA H02172
ADD AL,7
H02172:
CALL PrintHex
MOV AL,CH
AND AL,00001111b
ADD AL,30h
CMP AL,'9' ;39h
JNA H02181
ADD AL,7
H02181: CALL PrintHex
ADD HexPointer,2
POP AX
POP CX
RET
PrintHex:
MOV SI,HexPointer
MOV WORD PTR [SI+offset ScreenStart],AX
INC SI
INC SI
MOV HexPointer,SI
RET
; - - - - - - - - - - - - - - - - - -
ALtoHexInAX:
MOV AH,AL ;save AL
AND AL,00001111b ;get lower nibble
OR AL,00110000b ;30h
CMP AL,'9' ;39h
JNA H02198
ADD AL,7
H02198: MOV CL,4
SHR AH,CL ;get upper nibble in AH
OR AH,00110000b
CMP AH,'9' ;39h
JA H021A5
RET
H021A5: ADD AH,7
RET
; - - - - - - - - - - - - - - - - - -
Print1atAsciiP:
CMP GraphChars,0
JNZ ShowIt
CMP AL,' ' ;20h
JC H021CA
CMP AL,7Eh
JA H021CA
JMP ShowIt
H021CA: MOV AL,'.' ;2Eh
ShowIt: MOV SI,ASCIIpntr
MOV WORD PTR [SI+offset ScreenStart],AX
INC SI
INC SI
MOV ASCIIpntr,SI
RET
; - - - - - - - - - - - - - - - - - -
ShoCursors:
PUSH DX
PUSH CX
PUSH BX
PUSH AX
;in last record, if past end of file, put cursor at last byte
MOV AX,WORD PTR LastRecLo
CMP AX,WORD PTR CurrRecLo
MOV AL,ByteNo
JNZ NotTheLast
;we're in the last record
CMP AL,LastByte
JB NotTheLast
MOV AL,LastByte
MOV ByteNo,AL
NotTheLast:
MOV DI,1550 ;56th on 10th line
PUSH AX
PUSH ES
MOV ES,VideoSeg
CALL ALtoHexInAX
XCHG AL,AH
STOSB
INC DI
MOV AL,AH
STOSB
POP ES
POP AX
XOR AH,AH
MOV BL,10h
DIV BL ;AL = ByteNo/16d
XCHG AL,AH
ADD AH,2 ;AX = (ByteNo * 16d) + 512d
MOV DX,AX
ADD DL,3Eh
MOV BL,3
MUL BL
MOV AH,DH
ADD AL,5
MOV CH,ActCrsrAttr
MOV CL,PassCrsrAttr
CMP ActiveScrn,0
JZ ASCIIisActive
XCHG CH,CL
ASCIIisActive:
PUSH ES
MOV ES,VideoSeg
MOV BX,HexCrsrLocn
MOV SI,BX
MOV BL,BYTE PTR [SI+offset ScreenStart+1]
MOV BYTE PTR ES:1[SI],BL
MOV BYTE PTR ES:3[SI],BL
MOV BX,H0040C
MOV SI,BX
MOV BL,BYTE PTR [SI+offset ScreenStart+1]
MOV BYTE PTR ES:1[SI],BL
MOV BX,AX
MOV AL,AH
MOV AH,50h
MUL AH
XOR BH,BH
ADD AX,BX
SHL AX,1
MOV HexCrsrLocn,AX
MOV SI,AX
MOV BYTE PTR ES:1[SI],CH
MOV BYTE PTR ES:3[SI],CH
MOV AX,DX
MOV AL,AH
MOV AH,50h
MUL AH
XOR DH,DH
ADD AX,DX
SHL AX,1
MOV H0040C,AX
MOV SI,AX
MOV BYTE PTR ES:1[SI],CL
POP ES
POP AX
POP BX
POP CX
POP DX
RET
; - - - - - - - - - - - - - - - - - -
ShoOnMsgLine:
PUSH ES
MOV ES,WORD PTR DS:VideoSeg
MOV DI,3360
MOV AL,' '
CALL Paint62
ShoLoop:
LODSB
OR AL,AL
JZ ShoDone
STOSB
INC DI
JMP SHORT ShoLoop
ShoDone:
POP ES
RET
Paint62:
PUSH DI
PUSH CX
MOV CX,62
P62Loop:
STOSB
INC DI
LOOP P62Loop
POP CX
POP DI
RET
; - - - - - - - - - - - - - - - - - -
UpCaseAndCifNotASCII:
CMP AL,'a' ;61h
JB H02272
SUB AL,20h
H02272: CMP AL,' ' ;20h
JB NotASCII
CMP AL,'Z'
JA NotASCII
CLC
RET
NotASCII:
STC
RET
; - - - - - - - - - - - - - - - - - -
UpCaseLetter:
CMP AL,'a'
JB NoChg
CMP AL,'z'
JA NoChg
SUB AL,20h
NoChg: RET
; - - - - - - - - - - - - - - - - - -
PaintScreen:
PUSH ES
PUSH CX
MOV ES,WORD PTR DS:VideoSeg
XOR DI,DI
MOV SI,OFFSET ScreenStart
MOV CX,2000 ;Decimal
REP MOVSW
POP CX
POP ES
RET
SetCrsrType:
MOV AH,3 ;Read Cursor Position
INT 10h
MOV CrsrType,CX
MOV CL,2Fh ;Ending Scan Line
MOV CH,CL ;Starting Scan Line
MOV AH,1 ;Set Cursor Type
INT 10h
MOV AH,5 ;Select Display Page
MOV AL,0
INT 10h
RET
RestoreCrsr:
MOV AH,5 ;Select Display Page
MOV AL,0 ;page no.
INT 10h
MOV AH,1 ;Set Cursor Type
MOV CX,CrsrType
INT 10h
XOR AL,AL ;Is this a delay ?
CMP AL,0
JNZ H022E4
MOV AH,2 ;Set Cursor Position
MOV DX,1800h ;row 24, col 0
XOR BH,BH ;page 0
INT 10h
H022E4: RET
ShowCurrRec:
MOV DI,offset CurRec
MOV AX,WORD PTR DS:CurrRecLo
ShowRecNo:
CMP COMflag,0
JNZ One1st
DEC AX
One1st:
PUSH AX
CALL ALtoHexInAX
MOV BYTE PTR 4[DI],AH
MOV BYTE PTR 6[DI],AL
POP AX
MOV AL,AH
CALL ALtoHexInAX
MOV BYTE PTR [DI],AH
MOV BYTE PTR 2[DI],AL
CLC
RET
; - - - - - - - - - - - - - - - - - -
ShowFNameAndDate:
MOV SI,OFFSET FNameToShow
MOV DI,OFFSET FileNameLoc
MOV AL,' '
CALL Paint62
FNameLoop:
MOVSB
INC DI
CMP BYTE PTR DS:[SI],0
JNZ FNameLoop
MOV AH,57h ;Date & Time of File
XOR AL,AL ;Get it
MOV BX,Handle
PUSH DI
INT 21h
POP DI
ADD DI,4
MOV AX,DX ;date
SHR AX,1
MOV CL,4
SHR AL,CL
CALL AXtoDecimalAtDI
MOV BYTE PTR [DI],'/'
INC DI
INC DI
MOV AL,DL
AND AL,00011111b
CALL AXtoDecimalAtDI
MOV BYTE PTR [DI],'/'
INC DI
INC DI
MOV AL,DH
SHR AL,1
ADD AL,50h
JMP AXtoDecimalAtDI
; - - - - - - - - - - - - - - - - - -
ShowLineNos:
;set up for the byte numbers:
MOV HexPointer,12 ;6th char on 1st line
MOV BL,'0' ;the byte number to print
MOV AH,LineNoAttr
ShoByteNos:
MOV DI,HexPointer
MOV AL,BL
CALL PrintHex
ADD HexPointer,4
INC BL
CMP BL,':'
JNZ NoAdd
ADD BL,7
NoAdd: CMP BL,'F'
JNA ShoByteNos
;now set up for line nos
MOV HexPointer,320 ;160th char, 1st on 3rd line
XOR BL,BL ;the line number to print
MOV AH,LineNoAttr
ShoLineNos:
MOV DI,HexPointer
MOV AL,BL
CALL Print2atHexP
MOV DI,HexPointer
MOV BYTE PTR [DI+offset ScreenStart],'│'
ADD HexPointer,154 ;move up 77 more chars, to next line
ADD BL,10h
JNC ShoLineNos
RET
AXtoDecimalAtDI:
PUSH DX
XOR AH,AH
XOR DX,DX
MOV BYTE PTR [DI],'0'
XOR CL,CL
H02457: DIV WORD PTR DS:Ten
OR DL,00110000b
PUSH DX
XOR DL,DL
INC CL
CMP AX,0
JNZ H02457
H02468: POP DX
MOV BYTE PTR [DI],DL
INC DI
INC DI
DEC CL
JNZ H02468
POP DX
RET
; - - - - - - - - - - - - - - - - - -
;Copy attrib only for spaces between the hex nos
CopyHexDisplAttr:
MOV AL,HexDisplAttr
MOV DI,OFFSET HexSpaces
MOV AH,10h ;16d times thru entire routine
H0247A: MOV CX,0Fh ;15d times, show every 3rd char
H0247D: MOV BYTE PTR [DI],AL
ADD DI,6
LOOP H0247D
ADD DI,46h ;move up 36d characters
DEC AH
JNZ H0247A
RET
; - - - - - - - - - - - - - - - - - -
SetVideoSeg:
PUSH ES
MOV BX,40h ;BIOS data seg
MOV ES,BX
MOV BX,10h
MOV AL,BYTE PTR ES:[BX] ;Hardware byte
MOV BX,0B000h
AND AL,00110000b
CMP AL,30h ;80 X 25 mono ?
JZ SetIt
MOV BH,0B8h
SetIt: MOV VideoSeg,BX
POP ES
RET
; - - - - - - - - - - - - - - - - - -
GetTargetName:
XOR CH,CH
MOV CL,ParamCount
CMP CL,2
JC CmdLineEmpty
DEC CL
MOV SI,OFFSET CmdLineBuf
MOV DI,OFFSET FNameToShow
FNloop:
LODSB
CALL UpCaseAndCifNotASCII
STOSB
LOOP FNloop
;check .EXT
XCHG DI,SI
SUB SI,4
LODSB
CMP AL,'.'
JNZ NotCOM
LODSB
CMP AL,'C'
JNZ NotCOM
LODSB
CMP AL,'O'
JNZ NotCOM
LODSB
CMP AL,'M'
JNZ NotCOM
MOV COMflag,1
NotCOM: CLC
RET
CmdLineEmpty:
MOV DX,OFFSET NoNameMsg
MOV AH,9
INT 21h
STC
RET
; - - - - - - - - - - - - - - - - - -
GetFileStats:
MOV AH,42h ;Move File Pointer
MOV AL,2 ;to EOF + CX:DX
MOV BX,Handle
XOR DX,DX
XOR CX,CX
INT 21h
JC SizeErr
;Now size of file is in DX:AX
SUB AX,1 ;dec DX:AX so a 100h-byte file will not
SBB DL,0 ; use 2 records
MOV LastByte,AL ;to stop cursor at end of file
MOV AL,AH
MOV AH,DL
INC AX
MOV WORD PTR DS:LastRecLo,AX
;show the Last Record no.
MOV DI,offset LastRecLoc
JMP ShowRecNo
SizeErr:
STC
RET
OpenFile:
MOV WORD PTR DS:ErrCode,0
MOV DX,OFFSET FNameToShow
MOV AL,2
MOV AH,3Dh ;Open File
INT 21h
MOV Handle,AX
JNC OpenOK
MOV WORD PTR DS:ErrCode,AX
CMP AL,2
JC H0258E ;jmp if 1 or 0
CMP AL,5
JA H0258E
DEC AL
DEC AL
XOR DX,DX
MOV DL,AL
MOV CL,4
SHL DX,CL
ADD DX,OFFSET Err2
JMP SHORT ShoMsg
H0258E: AAM
XCHG AL,AH
OR WORD PTR DS:ErrCode,AX
MOV DX,OFFSET OpenErrMsg
ShoMsg:
MOV AH,9
INT 21h
MOV AH,9
MOV DX,OFFSET CrLf$
INT 21h
STC
RET
OpenOK: CLC
RET
; - - - - - - - - - - - - - - - - - -
;help routine
F1: PUSH ES
MOV ES,WORD PTR DS:VideoSeg
MOV DI,496 ;248th char , 9th on 4th line
MOV DH,HelpAttr
MOV AH,HelpBrdrAttr
MOV AL,'┌'
STOSW
MOV AL,'─'
MOV CX,62
REP STOSW
MOV AL,'┐'
STOSW
MOV DI,496+160
MOV DL,' '
MOV AL,'│'
MOV BX,17 ;no of lines inside the box
H025D0: STOSW
XCHG AX,DX
MOV CX,62 ;no of spaces inside the box
REP STOSW
XCHG AX,DX
STOSW
ADD DI,2*(80-64)
DEC BX
JNZ H025D0
MOV AL,'└'
STOSW
MOV SI,offset HelpBottom
MOV CX,62 ;length of string
MOV AL,AH
H025EA: MOVSB
STOSB
LOOP H025EA
MOV AL,'┘'
STOSW
PaintHelp: ;displays the Help text
;locate start of line
PUSH ES
MOV AX,DS
MOV ES,AX
MOV DI,offset HelpMsg
XOR AL,AL
XOR DL,DL
LocLoop:
CMP HelpLineCount,DL
JZ Located
MOV CX,62 ;chars displayed/line
REPNZ SCASB ;either 62 chars or a 0 are found
INC DL
JMP SHORT LocLoop
Located:
POP ES
MOV SI,DI
MOV DI,496+160+2 ;9th on 5th line
MOV BX,17 ;do 17d lines
HelpLine:
MOV CX,62 ;do 62d characters
HelpCharLoop:
LODSB
OR AL,AL
JZ PadLine
STOSB
INC DI
LOOP HelpCharLoop
CalcNext:
ADD DI,2*(80-62)
DEC BX
JNZ HelpLine
ReadHelpKbd:
XOR AH,AH ;Read Char from Kbd
INT 16h
CMP AH,3Bh ;scan code = F1 ?
JZ ExitHelp
CMP AH,1 ;Esc ?
JZ ExitHelp
CMP AH,4Bh
JA H02642
CMP HelpLineCount,0
JZ ReadHelpKbd
;we are not at the very top line
CMP AH,48h ;up arrow ?
JNZ H02634
DEC HelpLineCount
JMP SHORT PaintHelp
PadLine:
MOV AL,' '
STOSB
INC DI
LOOP PadLine
JMP CalcNext
H02634: CMP AH,49h ;pgup ?
JNZ ReadHelpKbd
SUB HelpLineCount,17 ;lines/page
JNS PaintHelp
MOV HelpLineCount,0 ;keep from going under 0
JMP PaintHelp
H02642: MOV DH,HelpLineCount
CMP DH,MaxMove
JZ ReadHelpKbd
CMP AH,50h ;down arrow ?
JNZ H02651
INC HelpLineCount
JMP PaintHelp
H02651: CMP AH,51h ;pgdn ?
JNZ ReadHelpKbd
ADD HelpLineCount,17 ;lines/page
MOV DH,MaxMove
CMP DH,HelpLineCount
JA ToPH
MOV HelpLineCount,DH
ToPH: JMP PaintHelp
ExitHelp:
POP ES
CALL PaintScreen
CALL ShoCursors
CLC
RET
CSEG ends
END Start